package com.visualexpress.count;

import java.util.Collections;
import java.util.Comparator;
import java.util.Iterator;
import java.util.List;

import com.visualexpress.dao.LocationAvertimeDAO;
import com.visualexpress.dao.RouteInfoDAO;
import com.visualexpress.dao.ShipmentDAO;
import com.visualexpress.dao.TimeLocationDAO;
import com.visualexpress.domain.Location;
import com.visualexpress.domain.LocationAvertime;
import com.visualexpress.domain.RouteInfo;
import com.visualexpress.domain.Shipment;
import com.visualexpress.domain.TimeLocation;
import com.visualexpress.util.DateUtil;


class CountRouteInfo {
	public static void addShipment(Shipment shipment) {
		TimeLocationDAO timeLocDAO = new TimeLocationDAO();
		RouteInfoDAO routeInfoDAO = new RouteInfoDAO();
		List<TimeLocation> timeLocationList = timeLocDAO.findByShipment(shipment);
		
		Collections.sort(timeLocationList,
			new Comparator<TimeLocation>() {
				public int compare(TimeLocation o1, TimeLocation o2) {
					return o1.getLocationNumber() - o2.getLocationNumber(); 
				}
			});
		
		int totalCities = timeLocationList.size();
		int i, j;
		TimeLocation startTimeLocation, endTimeLocation;
		Location startLocation, endLocation;
		RouteInfo routeInfo;
		for(i = 0; i < totalCities - 1; i++) {
			for(j = i + 1; j < totalCities; j++) {
				startTimeLocation = timeLocationList.get(i);
				endTimeLocation = timeLocationList.get(j);
				startLocation = startTimeLocation.getLocation();
				endLocation = endTimeLocation.getLocation();
				List<RouteInfo> lstRouteInfo = routeInfoDAO.findByStartAndEnd(startLocation, endLocation);
				if (lstRouteInfo.isEmpty()) {
					routeInfo = new RouteInfo();
					routeInfo.setFluent(1);
					routeInfo.setStartLocation(startLocation);
					routeInfo.setEndLocation(endLocation);
					routeInfo.setRecentTime(startTimeLocation.getLeaveTime());
					routeInfo.setTime(DateUtil.substractInHours(
							endTimeLocation.getArrivalTime(), startTimeLocation.getLeaveTime()));
					routeInfo.setWeight(1.0);
					routeInfoDAO.save(routeInfo);
				} else {
					double newWeight;
					double diminish;
					routeInfo = (RouteInfo) lstRouteInfo.get(0);
					routeInfo.setFluent(routeInfo.getFluent() + 1);
					if(startTimeLocation.getLeaveTime().before(routeInfo.getRecentTime())) {
						diminish = Diminish.diminish(DateUtil.substractInDays(routeInfo.getRecentTime()
								, startTimeLocation.getLeaveTime()));
						newWeight = 1 * diminish + routeInfo.getWeight();
						routeInfo.setTime((DateUtil.substractInHours(
								endTimeLocation.getArrivalTime(), startTimeLocation
										.getLeaveTime()) * diminish + routeInfo.getTime()
								* routeInfo.getWeight())
								/ newWeight);
					} else {
						diminish = Diminish.diminish(DateUtil.substractInDays(
								startTimeLocation.getLeaveTime(), routeInfo
										.getRecentTime()));
						newWeight = 1 + routeInfo.getWeight() * diminish;
						routeInfo.setTime((DateUtil.substractInHours(
								endTimeLocation.getArrivalTime(), startTimeLocation
										.getLeaveTime()) + routeInfo.getTime()
								* routeInfo.getWeight() * diminish)
								/ newWeight);
						routeInfo.setRecentTime(startTimeLocation.getLeaveTime());						
					}
					routeInfo.setWeight(newWeight);
					routeInfoDAO.attachDirty(routeInfo);
				}
			} //for:j
		} //for:i

	}
}
